package co.fitstart.entity.courseware.exercise;

import java.beans.Transient;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.ManyToOne;
import javax.persistence.Table;

import org.apache.commons.lang3.StringUtils;

import com.alibaba.fastjson.annotation.JSONField;
import com.fasterxml.jackson.annotation.JsonIdentityInfo;
import com.fasterxml.jackson.annotation.JsonIdentityReference;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import com.fasterxml.jackson.annotation.ObjectIdGenerators;

import co.fitstart.entity.courseware.fitnessgroup.BatchCourseware;

/**
 * 周计划-运动
 * @author haiyan_xiao
 *
 */
@Entity
@Table(name = "exercise")
@JsonIgnoreProperties(value={"hibernate_lazy_initializer","handler","fieldHandler"})
public class Exercise {
    @Id
    @GeneratedValue
    private Long id;
    
    /** 所属课件批次 */
    @ManyToOne(fetch = FetchType.LAZY, optional = false)
    @JSONField(serialize = false)
    @JsonIdentityInfo(generator=ObjectIdGenerators.PropertyGenerator.class, property="id")
    @JsonIdentityReference(alwaysAsId=true)
    private BatchCourseware batch;
    
    /** LISS低强度恒速有氧训练 */
    private String lissType;
    
    /** LISS低强度恒速有氧训练-其它 */
    private String otherLiss;
    
    /** HIT高强度间歇训练 */
    private String hit;
    
    /** 核心训练 */
    private String core;
    
    /** 教练备注 */
    private String remark;
    
    /** 家庭作业完成保证（次/周） */
    private Integer homeworkFrequency;
    
    /** 门店训练频率保证（次/周） */
    private Integer scheduleFrequency;
    
    private Date createTime;
    
    @Column(name = "is_disabled")
    private boolean disabled;
    
    public Exercise() {
        
    }
    
    /**
     * initialize
     * @param batch
     * @return
     */
    public Exercise initialize(BatchCourseware batch) {
        this.batch = batch;
        this.createTime = new Date();
        this.disabled = false;
        
        return this;
    }
    
    /**
     * edit
     * @param exercise
     * @return
     */
    public Exercise edit(Exercise exercise) {
        this.otherLiss = exercise.getOtherLiss();
        this.hit = exercise.getHit();
        this.core = exercise.getCore();
        this.remark = exercise.getRemark();
        this.homeworkFrequency = exercise.getHomeworkFrequency();
        this.scheduleFrequency = exercise.getScheduleFrequency();
        
        return this;
    }

    /**
     * 
     * @param homeworkFrequency
     * @param lissTypes
     * @param otherLiss
     * @param hit
     * @param core
     * @param remark
     * @return
     */
    public Exercise edit(Integer homeworkFrequency, List<LissType> lissTypes,
            String otherLiss, String hit, String core, String remark) {
        this.homeworkFrequency = homeworkFrequency;
        this.editLissType(lissTypes);
        this.otherLiss = otherLiss;
        this.hit = hit;
        this.core = core;
        this.remark = remark;
        return this;
    }
    
    /**
     * 
     * @return
     */
    public Exercise disable() {
        this.disabled = true;
        return this;
    }
    
    /**
     * 
     * @param lissTypes
     * @return
     */
    public Exercise editLissType(List<LissType> lissTypes) {
        if(lissTypes != null && !lissTypes.isEmpty()) {
            StringBuffer buffer = new StringBuffer();
            
            for(LissType lissType : lissTypes) {
                buffer.append(lissType.ordinal() + ",");
            }
            
            this.lissType = buffer.toString();
        } else {
            this.lissType = null;
        }
        
        return this;
    }
    
    /**
     * 
     * @return
     */
    @Transient
    public List<LissType> getLissTypeList() {
        List<LissType> lissTypes = new ArrayList<>();
        
        if(lissType != null) {
            String[] temps = lissType.split(",");
            
            if(temps != null && temps.length > 0) {
                for(String temp : temps) {
                    lissTypes.add(LissType.ordinalOf(Integer.parseInt(temp)));
                }
            }
        }
        
        return lissTypes;
    }

    /**
     * 
     * @return
     */
    public List<Map<String, Object>> getLisses() {
        List<Map<String, Object>> result = new ArrayList<>();
        
        List<LissType> lissTypes = this.getLissTypeList();
        for(LissType liss : LissType.values()) {
            Map<String, Object> map = new HashMap<>();
            map.put("name", liss.getDescription());
            map.put("value", liss);
            map.put("selected", lissTypes.contains(liss));
            result.add(map);
        }
        
        return result;
    }
    
    /**
     * 
     * @return
     */
    public String getLiss() {
        StringBuffer buffer = new StringBuffer();
        
        List<LissType> lissTypes = getLissTypeList();
        for(LissType type : lissTypes) {
            buffer.append(type.getDescription() + ",");
        }
        
        if(StringUtils.isNotBlank(otherLiss)) {
            return buffer.append(otherLiss).toString();
        } else {
            return buffer.length() == 0 ? buffer.toString() : buffer.substring(0, buffer.length() - 1);
        }
    }

    /**
     * @return the id
     */
    public Long getId() {
        return id;
    }

    /**
     * @return the batch
     */
    public BatchCourseware getBatch() {
        return batch;
    }

    /**
     * @return the lissType
     */
    public String getLissType() {
        return lissType;
    }

    /**
     * @return the otherLiss
     */
    public String getOtherLiss() {
        return otherLiss;
    }

    /**
     * @return the hit
     */
    public String getHit() {
        return hit;
    }

    /**
     * @return the core
     */
    public String getCore() {
        return core;
    }

    /**
     * @return the remark
     */
    public String getRemark() {
        return remark;
    }

    /**
     * @return the homeworkFrequency
     */
    public Integer getHomeworkFrequency() {
        return homeworkFrequency;
    }

    /**
     * @return the scheduleFrequency
     */
    public Integer getScheduleFrequency() {
        return scheduleFrequency;
    }

    /**
     * @return the createTime
     */
    public Date getCreateTime() {
        return createTime;
    }

    /**
     * @return the disabled
     */
    public boolean isDisabled() {
        return disabled;
    }

    /**
     * @param id the id to set
     */
    public void setId(Long id) {
        this.id = id;
    }

    /**
     * @param batch the batch to set
     */
    public void setBatch(BatchCourseware batch) {
        this.batch = batch;
    }

    /**
     * @param lissType the lissType to set
     */
    public void setLissType(String lissType) {
        this.lissType = lissType;
    }

    /**
     * @param otherLiss the otherLiss to set
     */
    public void setOtherLiss(String otherLiss) {
        this.otherLiss = otherLiss;
    }

    /**
     * @param hit the hit to set
     */
    public void setHit(String hit) {
        this.hit = hit;
    }

    /**
     * @param core the core to set
     */
    public void setCore(String core) {
        this.core = core;
    }

    /**
     * @param remark the remark to set
     */
    public void setRemark(String remark) {
        this.remark = remark;
    }

    /**
     * @param homeworkFrequency the homeworkFrequency to set
     */
    public void setHomeworkFrequency(Integer homeworkFrequency) {
        this.homeworkFrequency = homeworkFrequency;
    }

    /**
     * @param scheduleFrequency the scheduleFrequency to set
     */
    public void setScheduleFrequency(Integer scheduleFrequency) {
        this.scheduleFrequency = scheduleFrequency;
    }

    /**
     * @param createTime the createTime to set
     */
    public void setCreateTime(Date createTime) {
        this.createTime = createTime;
    }

    /**
     * @param disabled the disabled to set
     */
    public void setDisabled(boolean disabled) {
        this.disabled = disabled;
    }
}
